from PySFML import sf
from camera import camera
import ConfigParser
import sys, os
import image

class animation (sf.Sprite) :
    """ Generic animation extention of the sf.Sprite object """
    def __init__ (self) :
        self.num_frames = 0
        self.x = 0
        self.y = 0
        self.frames = []
        self.durations = []
        self.current_duration = 0.0
        self.current_frame_num = 0
        self.current_frame = None
        self.time = 0.0
        self.camera = camera ()
    def __del__ (self) :
        """ todo: write this """
        pass
    def set_position (self, x , y) :
        """ Set the animation's world cords """
        self.x = x
        self.y = y
    def add_frame (self, frame, duration) :
        """ Add a frame to the animation """
        if self.num_frames == 0 : 
            sf.Sprite.__init__ (self, frame)
        self.frames.append (frame)
        self.durations.append (duration)
        self.num_frames += 1
        self.current_frame = self.frames[0]
        self.current_duration = self.durations[0]
    def update (self, dt) :
        """ Update this animation to the next frame if it is time """
        self.time += dt
        if self.time >= self.current_duration :
            self.current_frame_num += 1
            self.time = 0
            if self.current_frame_num >= self.num_frames :
                self.current_frame_num = 0
            self.SetImage (self.frames[self.current_frame_num])
            self.current_duration = self.durations[self.current_frame_num]
    def draw (self) :
        """ Draw the sprite to the screen"""
        self.camera.draw_sprite (self)
    def load (self, ini_file, section_name) :
        """ Load frames from an ini file """
        ini = ConfigParser.ConfigParser()
        ini.read (os.path.join ('data', ini_file))
        for im, duration in ini.items (section_name) :
            self.add_frame (image.load (im), int (duration))
        del ini
        
class tiler_noclip (object) :
    """ A tiler that does not clip the image to be exactly the length
        provided """
    def __init__ (self, frame, x, x2, y) :
        self.image = frame
        self.x = x
        self.x2 = x2
        self.y = y
        self.image_size_x, self.image_size_y = self.image.GetWidth (), self.image.GetHeight ()
        self.tiled_num = ((x2 - x) / self.image_size_x) + 1
        self.sprites = []
        self.camera = camera ()
        for i in range (self.tiled_num) :
            self.sprites.append (animation_single (self.image))
            self.sprites[i].set_position (self.x + (i * self.image_size_x), self.y)
    def resize (self, x, x2) :
        if not x == None :
            self.x = x
        if not x2 == None :
            self.x2 = x2
        tiled_num_new = ((x2 - x) / self.image_size_x) + 1
        if tiled_num_new < tiled_num :
            for i in range (tiled_num - tiled_num_new) :
                self.sprites.pop ()
        else :
            for i in range (tiled_num + 1, tiled_num_new) :
                self.sprites.append (animation_single (self.image))
                self.sprites[i].set_position (self.x + (i * self.image_size_x), self.y)
    def draw (self) :
        for sprite in self.sprites :
            self.camera.draw_sprite (sprite)

class tiler (object) :
    def __init__ (self, frame, x, x2, y) :
        self.image = frame
        self.x = x
        self.x2 =x2
        self.y = y
        self.image_size_x, self.image_size_y = self.image.GetWidth (), self.image.GetHeight ()
        self.tiled_num = (x2 - x) / self.image_size_x
        self.sprites = []
        self.camera = camera ()
        self.part = (self.tiled_num * self.image_size_x) + self.x
        part_rect = sf.IntRect (0, 0, self.x2 - self.part, self.image_size_y)
        for i in range (self.tiled_num + 1) :
            self.sprites.append (animation_single (self.image))
            self.sprites[i].set_position (self.x + (i * self.image_size_x), self.y)
        self.sprites[i].SetSubRect (part_rect)
    def draw (self) :
        for sprite in self.sprites :
            self.camera.draw_sprite (sprite)

class animation_single (sf.Sprite) :
    def __init__ (self, frame) :
        self.x = 0
        self.y = 0
        self.camera = camera ()
        sf.Sprite.__init__ (self, frame)
    def __del__ (self) :
        pass
    def set_position (self, x, y) :
        self.x = x
        self.y = y
    def draw (self) :
        self.camera.draw_sprite (self)
